<?php
namespace app\common\service;

class DateService
{
    /**
     * 查询指定时间范围内的所有日期，月份，季度，年份
     *
     * @param string $st 指定开始时间
     * @param string $et 指定结束时间
     * @param string $type 类型，day 天，month 月份，quarter 季度，year 年份
     * @param string $format 时间格式
     * @return array
     */
    public function getDateByInterval(string $st, string $et, string $type = 'day', string $format = 'Y-m-d')
    {
        // 日期格式不正确
        $startTime = strtotime($st);
        $endTime = strtotime($et);

        if ($startTime === false || $endTime === false || $startTime > $endTime) {
            return [];
        }

        switch ($type) {
            case 'day':
                return $this->generateDailyRange($startTime, $endTime, $format);
            case 'month':
                return $this->generateMonthlyRange($startTime, $endTime, $format);
            case 'quarter':
                return $this->generateQuarterlyRange($startTime, $endTime, $format);
            case 'year':
                return $this->generateYearlyRange($startTime, $endTime, $format);
            default:
                return [];
        }
    }

    /**
     * 生成日期范围
     */
    private function generateDailyRange(int $startTime, int $endTime, string $format): array
    {
        $result = [];
        $currentTime = $startTime;

        while ($currentTime <= $endTime) {
            $date = date('Y-m-d', $currentTime);
            $result[] = [
                'name' => $date,
                'startDate' => $date,
                'endDate' => $date,
                'format' => date($format, $currentTime)
            ];
            $currentTime = strtotime('+1 day', $currentTime);
        }

        return $result;
    }

    /**
     * 生成月份范围
     */
    private function generateMonthlyRange(int $startTime, int $endTime, string $format): array
    {
        $result = [];
        $currentTime = strtotime('first day of this month', $startTime);

        while ($currentTime <= $endTime) {
            $startDate = date('Y-m-01', $currentTime);
            $endDate = date('Y-m-t', $currentTime);

            $result[] = [
                'name' => date('Y-m', $currentTime),
                'startDate' => $startDate,
                'endDate' => $endDate,
                'format' => date($format, $currentTime)
            ];

            $currentTime = strtotime('first day of next month', $currentTime);
        }

        return $result;
    }

    /**
     * 生成季度范围
     */
    private function generateQuarterlyRange(int $startTime, int $endTime, string $format): array
    {
        $result = [];
        $currentYear = date('Y', $startTime);
        $currentQuarter = ceil(date('n', $startTime) / 3);
        $currentTime = mktime(0, 0, 0, ($currentQuarter - 1) * 3 + 1, 1, $currentYear);

        while ($currentTime <= $endTime) {
            $quarter = ceil(date('n', $currentTime) / 3);
            $startMonth = ($quarter - 1) * 3 + 1;
            $endMonth = $quarter * 3;

            $startDate = date('Y-m-01', mktime(0, 0, 0, $startMonth, 1, date('Y', $currentTime)));
            $endDate = date('Y-m-t', mktime(0, 0, 0, $endMonth, 1, date('Y', $currentTime)));

            $result[] = [
                'name' => date('Y', $currentTime) . '第' . $quarter . '季度',
                'startDate' => $startDate,
                'endDate' => $endDate,
                'format' => date($format, $currentTime)
            ];

            $currentTime = strtotime('+3 months', $currentTime);
        }

        return $result;
    }

    /**
     * 生成年份范围
     */
    private function generateYearlyRange(int $startTime, int $endTime, string $format): array
    {
        $result = [];
        $currentYear = date('Y', $startTime);
        $currentTime = mktime(0, 0, 0, 1, 1, $currentYear);

        while ($currentTime <= $endTime) {
            $year = date('Y', $currentTime);
            $result[] = [
                'name' => $year . '年',
                'startDate' => date('Y-01-01', $currentTime),
                'endDate' => date('Y-12-31', $currentTime),
                'format' => date($format, $currentTime)
            ];

            $currentTime = strtotime('+1 year', $currentTime);
        }

        return $result;
    }

    /**
     * 时长转换
     *
     * @param string $timediff 秒数
     * @param integer $is_hour
     * @param integer $is_minutes
     * @return void
     */
    public static function getTimeHour($timediff = '', $is_hour = 1, $is_minutes = 1)
    {
        if (empty($timediff) || $timediff <= 60) {
            return '';
        }
        $day = floor($timediff / (3600 * 24));
        $day = $day > 0 ? $day . '天' : '';
        $hour = floor(($timediff % (3600 * 24)) / 3600);
        $hour = $hour > 0 ? $hour . '小时' : '';
        if ($is_hour && $is_minutes) {
            $minutes = floor((($timediff % (3600 * 24)) % 3600) / 60);
            $minutes = $minutes > 0 ? $minutes . '分钟' : '';
            return $day . $hour . $minutes;
        }

        if ($hour) {
            return $day . $hour;
        }
        return $day;
    }

    /**
     * 获取日期区间内的所有日期（适用于船票价格计算）
     * @param string $startDate 开始日期
     * @param string $endDate 结束日期
     * @return array
     */
    public function getDateRangeByInterval(string $startDate, string $endDate)
    {
        $start = new \DateTime($startDate);
        $end = new \DateTime($endDate);
        $interval = new \DateInterval('P1D');
        $period = new \DatePeriod($start, $interval, $end->modify('+1 day'));

        $dates = [];
        foreach ($period as $date) {
            $dates[] = [
                'name' => $date->format('Y-m-d'),
                'value' => $date->format('Y-m-d')
            ];
        }

        return $dates;
    }
}